package com.yunsc.order.sevice.impl;

import com.alibaba.fastjson.JSON;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.yunsc.common.exception.YunscException;
import com.yunsc.common.utils.DateUtils;
import com.yunsc.common.utils.PageResult;
import com.yunsc.media.service.YunscUploadFileService;
import com.yunsc.order.dao.YunscOrderDao;
import com.yunsc.order.dao.YunscRechargeOrderDao;
import com.yunsc.order.dto.OrderCommentDTO;
import com.yunsc.order.dto.OrderDeliveryDTO;
import com.yunsc.order.dto.QueryOrderDTO;
import com.yunsc.order.entity.*;
import com.yunsc.order.handler.impl.RedisDelayQueueEnum;
import com.yunsc.order.sevice.*;
import com.yunsc.order.utils.RedisDelayQueueUtil;
import com.yunsc.order.utils.RedisIdWorker;
import com.yunsc.order.vo.*;
import com.yunsc.product.entity.YunscCommentEntity;
import com.yunsc.product.entity.YunscCommentImageEntity;
import com.yunsc.product.service.YunscCommentImageService;
import com.yunsc.product.service.YunscCommentService;
import com.yunsc.product.service.YunscGoodsService;
import com.yunsc.store.dao.YunscRegionDao;
import com.yunsc.store.entity.YunscUserEntity;
import com.yunsc.store.service.*;
import com.yunsc.store.vo.OrderSettingVO;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang.StringUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;

import javax.annotation.Resource;
import java.math.BigDecimal;
import java.math.RoundingMode;
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.time.ZoneOffset;
import java.time.format.DateTimeFormatter;
import java.time.temporal.ChronoUnit;
import java.util.*;
import java.util.concurrent.TimeUnit;
import java.util.stream.Collectors;

import static com.yunsc.common.utils.DateUtils.convertDateToSeconds;

@Slf4j
@Service("yunscOrderService")
public class YunscOrderServiceImpl extends ServiceImpl<YunscOrderDao, YunscOrderEntity> implements YunscOrderService {

    @Resource
    private YunscUploadFileService uploadFileService;
    @Resource
    private YunscOrderGoodsService orderGoodsService;
    @Resource
    private YunscOrderAddressService orderAddressService;
    @Resource
    private YunscUserService userService;
    @Resource
    private YunscOrderDeliveryGoodsService orderDeliveryGoodsService;
    @Resource
    private YunscOrderDeliveryService orderDeliveryService;
    @Resource
    private YunscRegionDao regionDao;
    @Resource
    private YunscOrderRefundService orderRefundService;
    @Resource
    private RedisIdWorker redisIdWorker;
    @Resource
    private YunscUserPointsLogService userPointsLogService;
    @Resource
    private YunscCommentService commentService;
    @Resource
    private YunscCommentImageService commentImageService;
    @Resource
    private YunscUserCouponService userCouponService;
    @Resource
    private YunscStoreService storeService;
    @Resource
    private YunscGoodsService goodsService;
    @Resource
    private YunscStoreSettingService storeSettingService;
    @Resource
    private YunscRechargeOrderDao rechargeOrderDao;
    @Resource
    private RedisDelayQueueUtil redisDelayQueueUtil;

    @Override
    public PageResult<OrderDetailVO> queryOrderList(QueryOrderDTO params, Integer storeId) {
        int startTime = convertDateToSeconds(params.getBetweenTimeStart());
        int endTime = convertDateToSeconds(params.getBetweenTimeEnd());
        Page<OrderDetailVO> page = new Page<>(params.getPage(), params.getPageSize());

        Page<OrderDetailVO> pageResult = this.baseMapper.selectOrderList(page, params, startTime, endTime, storeId);
        pageResult.getRecords().forEach(detail -> {
            detail.getGoods().forEach(goods -> {
                Integer imageId = goods.getImageId();
                goods.setGoodsImage(uploadFileService.queryFileUrlById(imageId));
                goods.setGoodsProps(JSON.parseObject(goods.getGoodsProps().toString(), List.class));
            });
            detail.getUser().setAvatarUrl(uploadFileService.queryFileUrlById(detail.getUser().getAvatarId()));
            detail.getAddress().setRegion(regionDao.getAddressByOrderId(detail.getAddress().getRegionId()));
        });
        // 格式化分页结果
        return PageResult.formatPageResult(pageResult.getRecords(), params.getPage(), params.getPageSize(), pageResult.getTotal());
    }

    @Override
    public OrderDetailVO queryOrderDetailByOrderId(Integer orderId) {
        // 1、获取订单信息
        YunscOrderEntity order = this.getById(orderId);
        if (order == null) {
            return null;
        }
        OrderDetailVO orderDetail = new OrderDetailVO();
        BeanUtils.copyProperties(order, orderDetail);
        // 根据订单id获取地址信息
        YunscOrderAddressEntity orderAddress = orderAddressService.queryAddressByOrderId(orderId);
        orderDetail.setAddress(orderAddress);
        // 获取订单关联商品信息
        orderDetail.setGoods(queryOrderGoods(orderId));
        setOrderStateText(orderDetail);
        // update_price
        Object updatePrice = orderDetail.getUpdatePrice();
        Map<String, String> map = formatUpdatePrice(updatePrice.toString());
        orderDetail.setUpdatePrice(map);
        // 获取订单用户
        YunscUserEntity user = userService.getById(order.getUserId());
        YunscUserEntity userEntity = new YunscUserEntity();
        userEntity.setUserId(user.getUserId());
        userEntity.setNickName(user.getNickName());
        userEntity.setAvatarUrl(uploadFileService.queryFileUrlById(user.getAvatarId()));
        orderDetail.setUser(userEntity);
        // 获取物流信息
        List<OrderDeliveryVO> delivery = orderDeliveryService.queryDeliveryByOrderId(orderId);
        orderDetail.setDelivery(delivery);
        return orderDetail;
    }

    @Override
    @Transactional
    public void orderDelivery(OrderDeliveryDTO orderDeliveryDTO) {
        OrderDeliveryDTO.OrderExpressForm deliveryDTOForm = orderDeliveryDTO.getForm();
        Integer expressId = deliveryDTOForm.getExpressId();
        String expressNo = deliveryDTOForm.getExpressNo();
        Integer orderId = orderDeliveryDTO.getOrderId();
        Integer deliveryMethod = deliveryDTOForm.getDeliveryMethod(); // 配送方式
        List<OrderDeliveryDTO.PackGoodsData> packGoodsData = deliveryDTOForm.getPackGoodsData();
        YunscOrderEntity orderEntity = this.getById(orderId);
        if (orderEntity == null) {
            throw new YunscException("订单不存在");
        }
        Integer storeId = orderEntity.getStoreId();

        // 获取订单商品数量
        List<YunscOrderGoodsEntity> orderGoodsList = orderGoodsService.list(new LambdaQueryWrapper<YunscOrderGoodsEntity>().eq(YunscOrderGoodsEntity::getOrderId, orderId));
        if (CollectionUtils.isEmpty(orderGoodsList)) {
            throw new YunscException("订单商品不存在");
        }
        // 待发货商品总数量
        int sum = orderGoodsList.stream().mapToInt(YunscOrderGoodsEntity::getTotalNum).sum();
        // 发货商品数量
        int deliveryNum = packGoodsData.stream().mapToInt(OrderDeliveryDTO.PackGoodsData::getDeliveryNum).sum();
        // 获取已发货商品数量
        int deliveryNumCount = orderGoodsList.stream().mapToInt(YunscOrderGoodsEntity::getDeliveryNum).sum();
        // 发货商品总数量
        deliveryNum += deliveryNumCount;
        // 校验发货商品数量是否超出订单商品总数量
        if (deliveryNum > sum) {
            throw new YunscException("发货商品数量超出订单商品总数量");
        }

        // 1 记录发货记录
        YunscOrderDeliveryEntity orderDelivery = new YunscOrderDeliveryEntity();
        orderDelivery.setOrderId(orderId);
        orderDelivery.setDeliveryMethod(deliveryMethod);
        orderDelivery.setExpressId(expressId);
        orderDelivery.setExpressNo(expressNo);
        orderDelivery.setStoreId(storeId);
        boolean save = orderDeliveryService.save(orderDelivery);
        if (!save) {
            throw new YunscException("订单发货记录保存失败");
        }
        // 订单商品发货状态
        List<YunscOrderGoodsEntity> orderGoodsEntityList = new ArrayList<>();
        // 订单商品发货信息
        List<YunscOrderDeliveryGoodsEntity> orderDeliveryGoodsList = new ArrayList<>();

        // 记录订单商品状态
        packGoodsData.forEach(item -> {
            Integer orderGoodsId = item.getOrderGoodsId();
            orderGoodsList.stream().filter(orderGoods -> orderGoods.getOrderGoodsId().equals(orderGoodsId)).findFirst().ifPresent(orderGoods -> {
                Integer goodsDeliveryNum = item.getDeliveryNum();
                goodsDeliveryNum += orderGoods.getDeliveryNum();
                orderGoods.setDeliveryStatus(Objects.equals(goodsDeliveryNum, orderGoods.getTotalNum()) ? 20 : 30);
                orderGoods.setDeliveryNum(goodsDeliveryNum);
                orderGoodsEntityList.add(orderGoods);
                // 记录订单发货商品
                YunscOrderDeliveryGoodsEntity deliveryGoodsEntity = new YunscOrderDeliveryGoodsEntity();
                deliveryGoodsEntity.setOrderId(orderId);
                deliveryGoodsEntity.setDeliveryId(orderDelivery.getDeliveryId());
                deliveryGoodsEntity.setOrderGoodsId(orderGoods.getOrderGoodsId());
                deliveryGoodsEntity.setGoodsId(orderGoods.getGoodsId());
                deliveryGoodsEntity.setDeliveryNum(goodsDeliveryNum);
                deliveryGoodsEntity.setStoreId(storeId);
                orderDeliveryGoodsList.add(deliveryGoodsEntity);
            });
        });
        // 2 修改商品订单发货状态
        orderGoodsService.updateBatchById(orderGoodsEntityList);

        // 3 保存订单商品发货信息
        boolean saveBatch = orderDeliveryGoodsService.saveBatch(orderDeliveryGoodsList);
        if (!saveBatch) {
            throw new YunscException("订单发货商品记录保存失败");
        }

        // 4 修改订单状态
        boolean update = this.update(new UpdateWrapper<YunscOrderEntity>()
                .eq("order_id", orderId)
                .set("express_id", expressId)
                .set("express_no", expressNo)
                .set("delivery_status", sum == deliveryNum ? 20 : 30)   // 发货状态(10未发货 20已发货 30部分发货)
                .set("delivery_type", deliveryMethod)
                .set("delivery_time", new Date())
        );
        if (!update) {
            throw new YunscException("订单状态修改失败");
        }

        if (sum == deliveryNum){
            // 订单自动收货：订单状态为20已发货
            // 添加redission延迟队列，订单自动收货
            // 获取已发货的订单商品id
            Map<String, Object> map = new HashMap<>();
            map.put("orderId", orderEntity.getOrderId());
            map.put("remark", "订单自动收货");
            // 获取系统配置的超时时间
            OrderSettingVO orderSettingVO = storeSettingService.queryOrderSettingVO(storeId);
            String receiveDays = orderSettingVO.getOrder().getReceiveDays();// 自动收货时间（天）
            if (receiveDays == null || !receiveDays.equals("0")){
                // 取消订单自动收货
                return;
            }
            // 超时时间（秒）
            int timeoutSeconds = (int) (System.currentTimeMillis() / 1000) + (Integer.parseInt(receiveDays) * 24 * 60 * 60);
            // 添加订单自动收货任务
            redisDelayQueueUtil.addDelayQueue(map, timeoutSeconds, TimeUnit.SECONDS, RedisDelayQueueEnum.ORDER_TIMEOUT_NOT_RECEIVED.getCode());
            log.info("订单自动收货，订单号：{}, 超时时间：{}", orderId, timeoutSeconds);
        }
    }

    @Override
    public void updateRemark(OrderDeliveryDTO param) {
        Integer orderId = param.getOrderId();
        if (orderId == null) {
            throw new YunscException("订单id不能为空");
        }
        String remark = param.getForm().getContent();
        if (StringUtils.isEmpty(remark)) {
            throw new YunscException("备注不能为空");
        }
        this.update(new UpdateWrapper<YunscOrderEntity>()
                .eq("order_id", orderId)
                .set("merchant_remark", remark));
    }

    @Override
    public void deleteOrderById(Integer orderId) {
        // 逻辑删除订单
        this.update(new UpdateWrapper<YunscOrderEntity>().eq("order_id", orderId).set("is_delete", 1));
    }


    /**
     * 根据订单id获取商品信息
     *
     * @param orderId
     * @return
     */
    @Override
    public List<OrderGoodsVO> queryOrderGoods(Integer orderId) {
        LambdaQueryWrapper<YunscOrderGoodsEntity> queryWrapper = new LambdaQueryWrapper<YunscOrderGoodsEntity>()
                .eq(YunscOrderGoodsEntity::getOrderId, orderId);
        List<YunscOrderGoodsEntity> orderGoodsEntities = orderGoodsService.list(queryWrapper);
        List<OrderGoodsVO> collect = orderGoodsEntities.stream().map(item -> {
            OrderGoodsVO orderGoodsVO = new OrderGoodsVO();
            BeanUtils.copyProperties(item, orderGoodsVO);
            orderGoodsVO.setGoodsImage(uploadFileService.queryFileUrlById(item.getImageId()));
            orderGoodsVO.setGoodsProps(JSON.parseObject(item.getGoodsProps(), List.class));
            return orderGoodsVO;
        }).collect(Collectors.toList());
        return collect;
    }

    @Override
    public TodoCountsVO queryUserTodoCounts(Integer userId) {
        // 查询用户订单
        List<YunscOrderEntity> userOrders = this.list(new QueryWrapper<YunscOrderEntity>()
                .eq("user_id", userId)
                .in("order_status", 10, 21)
        );

        // 付款状态(10未付款 20已付款)
        List<YunscOrderEntity> payOrders = userOrders.stream().
                filter(order -> order.getPayStatus() == 20).collect(Collectors.toList());
        // 统计待发货订单 delivery_status 发货状态(10未发货 20已发货 30部分发货)
        long deliveryOrders = payOrders.stream().filter(order -> order.getDeliveryStatus() != 20).count();
        // 统计待收货订单 receipt_status 收货状态(10未收货 20已收货)
        long receiptOrders = payOrders.stream()
                // .filter(order -> order.getOrderStatus() != 30)
                .filter(order -> order.getDeliveryStatus() == 20)
                .filter(order -> order.getReceiptStatus() == 10).count();
        // 统计待付款订单 pay_status 支付状态(10未付款 20已付款)
        long disPayOrders = userOrders.stream().filter(order -> order.getPayStatus() == 10).count();
        // 统计售后订单 refund_status 退款状态(10未退款 20已退款)
        List<YunscOrderRefundEntity> orderRefunds = orderRefundService.list(new QueryWrapper<YunscOrderRefundEntity>().eq("user_id", userId));
        long orderRefundTotal = orderRefunds.stream().filter(order -> order.getStatus() == 0).count();

        TodoCountsVO userOrderCounts = new TodoCountsVO();
        userOrderCounts.setDelivery((int) deliveryOrders);
        userOrderCounts.setReceived((int) receiptOrders);
        userOrderCounts.setPayment((int) disPayOrders);
        userOrderCounts.setRefund((int) orderRefundTotal);

        return userOrderCounts;
    }

    @Override
    public YunscOrderEntity saveOrderDb(Integer userId, String remark, CheckOrderVO order, String platform) {
        YunscOrderEntity orderEntity = new YunscOrderEntity();

        BeanUtils.copyProperties(order, orderEntity);
        orderEntity.setUserId(userId);
        // 订单编号
        long orderNo = redisIdWorker.nextId("order");
        orderEntity.setPayPrice(order.getOrderPayPrice());
        // 订单号
        orderEntity.setOrderNo(String.valueOf(orderNo));
        // 订单总价格（优惠前）
        orderEntity.setTotalPrice(order.getOrderTotalPrice());
        // 订单价格 （优惠后）
        orderEntity.setOrderPrice(order.getOrderPrice());
        // 买家留言
        if (remark != null) {
            orderEntity.setBuyerRemark(remark);
        }
        // 支付状态
        orderEntity.setPayStatus(10);
        // 配送方式
        orderEntity.setDeliveryType(order.getDelivery());
        // 来源客户端
        orderEntity.setPlatform(platform);
        // 店铺id
        orderEntity.setStoreId(order.getStoreId());

        if (order.getIsUsePoints() == 0) {
            orderEntity.setPointsNum(0);
            orderEntity.setPointsMoney("0");
        }
        // 添加订单表
        boolean orderSave = this.save(orderEntity);
        if (!orderSave) {
            log.error("创建订单异常");
            throw new YunscException("创建订单异常");
        }

        // 更新优惠券状态
        Integer couponId = order.getCouponId();
        if (couponId != null && couponId > 0) {
            userCouponService.update().eq("user_id", orderEntity.getUserId()).eq("coupon_id", couponId)
                    .set("is_use", 1).update();
        }

        return orderEntity;
    }

    @Override
    public PageResult<OrderDetailVO> queryUserOrderList(QueryOrderDTO param, Integer userId) {
        Page<OrderDetailVO> page = new Page<>(param.getPage(), param.getPageSize());
        Page<OrderDetailVO> pageResult = this.baseMapper.selectUserOrderList(page, param.getDataType(), userId);
        pageResult.getRecords().forEach(detail -> {
            detail.getGoods().forEach(goods -> {
                goods.setGoodsImage(uploadFileService.queryFileUrlById(goods.getImageId()));
                // 解析商品规格属性
                Object goodsProps = goods.getGoodsProps();
                if (goodsProps != null) {
                    List<Map<String, Object>> goodsPropsList = JSON.parseObject(goodsProps.toString(), List.class);
                    goods.setGoodsProps(goodsPropsList);
                }

            });
            this.setOrderStateText(detail);
            Map<String, String> map = formatUpdatePrice(detail.getUpdatePrice().toString());
            detail.setUpdatePrice(map);
        });

        return PageResult.formatPageResult(pageResult.getRecords(), param.getPage(), param.getPageSize(), pageResult.getTotal());
    }

    @Override
    @Transactional
    public void cancelOrder(Integer orderId, Integer userId) {
        YunscOrderEntity orderEntity = this.getOne(new QueryWrapper<YunscOrderEntity>()
                .eq("order_id", orderId).eq("user_id", userId));
        if (orderEntity == null) {
            throw new YunscException("订单不存在");
        }
        if (orderEntity.getPayStatus() == 10) {
            // 订单未支付，直接取消订单
            orderEntity.setOrderStatus(20);
            // 返还用户积分
            Integer pointsNum = orderEntity.getPointsNum();
            if (pointsNum != null && pointsNum > 0) {
                // 返还用户积分
                userService.updateUserPoints(userId, pointsNum, "订单：" + orderEntity.getOrderNo() + "，取消返还积分");
                // userPointsLogService.addPointsLog(userId, pointsNum, "订单：" + orderEntity.getOrderNo() + "取消返还积分", orderEntity.getStoreId());
            }

        } else if (orderEntity.getPayStatus() == 20) {
            // 订单已支付，申请取消订单
            orderEntity.setOrderStatus(21);
        } else {
            throw new YunscException("订单状态异常");
        }
        this.updateById(orderEntity);
    }

    @Override
    public void receiptOrder(int orderId, Integer userId) {
        YunscOrderEntity orderEntity = this.getOne(new QueryWrapper<YunscOrderEntity>()
                .eq("order_id", orderId)
                .eq("user_id", userId));
        orderEntity.setOrderStatus(30);
        orderEntity.setReceiptStatus(20);
        orderEntity.setIsSettled(1);
        this.updateById(orderEntity);

        Integer pointsBonus = orderEntity.getPointsBonus();
        if (pointsBonus != null && pointsBonus > 0) {
            // 赠送积分
            userPointsLogService.addPointsLog(userId, pointsBonus, "订单：" + orderEntity.getOrderNo() + "，赠送积分", orderEntity.getStoreId());
        }

        // 订单自动好评
        // 添加redission延迟队列，订单自动好评
        // 获取系统配置的超时时间
        OrderSettingVO orderSettingVO = storeSettingService.queryOrderSettingVO(orderEntity.getStoreId());
        String evaluateDays = orderSettingVO.getOrder().getEvaluateDays();
        if (evaluateDays == null || !evaluateDays.equals("0")){
            // 取消订单自动好评
            return;
        }
        // 获取已发货的订单商品id
        Map<String, Object> map = new HashMap<>();
        map.put("orderId", orderEntity.getOrderId());
        map.put("remark", "订单自动好评");
        // 超时时间（秒）
        int timeoutSeconds = (int) (System.currentTimeMillis() / 1000) + (Integer.parseInt(evaluateDays) * 24 * 60 * 60);
        // 添加订单自动评价任务
        redisDelayQueueUtil.addDelayQueue(map, timeoutSeconds, TimeUnit.SECONDS, RedisDelayQueueEnum.ORDER_TIMEOUT_NOT_EVALUATED.getCode());
        log.info("订单超时未评价，系统默认好评，订单号：{}, 超时时间：{}", orderId, timeoutSeconds);

    }

    @Override
    @Transactional
    public void submitOrderComment(OrderCommentDTO params, Integer userId) {
        List<OrderCommentDTO.OrderCommentForm> form = params.getForm();
        Integer orderId = params.getOrderId();
        YunscOrderEntity order = this.getById(orderId);
        for (OrderCommentDTO.OrderCommentForm commentForm : form) {
            LambdaQueryWrapper<YunscCommentEntity> lqw = new LambdaQueryWrapper<>();
            lqw.eq(YunscCommentEntity::getOrderId, orderId)
                    .eq(YunscCommentEntity::getUserId, userId)
                    .eq(YunscCommentEntity::getOrderGoodsId, commentForm.getOrderGoodsId())
                    .eq(YunscCommentEntity::getStoreId, order.getStoreId());
            int commentNum = commentService.count(lqw);
            if (commentNum > 0) {
                // 订单已评价
                continue;
            }
            YunscCommentEntity comment = new YunscCommentEntity();
            comment.setScore(commentForm.getScore());
            comment.setContent(commentForm.getContent());
            comment.setUserId(userId);
            comment.setGoodsId(commentForm.getGoodsId());
            comment.setStoreId(order.getStoreId());
            comment.setOrderId(orderId);
            comment.setOrderGoodsId(commentForm.getOrderGoodsId());
            if (!CollectionUtils.isEmpty(commentForm.getImageList())) {
                comment.setIsPicture(1);
            }

            // 1、保存订单评价
            boolean saveComment = commentService.save(comment);
            if (!saveComment) {
                throw new YunscException("保存订单评价失败");
            }

            // 2、保存订单评价图片
            List<Integer> fileIds = commentForm.getUploaded();
            if (!CollectionUtils.isEmpty(fileIds)) {
                List<YunscCommentImageEntity> commentImages = new ArrayList<>();
                for (Integer fileId : fileIds) {
                    YunscCommentImageEntity commentImage = new YunscCommentImageEntity();
                    commentImage.setCommentId(comment.getCommentId());
                    commentImage.setStoreId(10001);
                    commentImage.setImageId(fileId);
                    commentImages.add(commentImage);
                }
                boolean saveBatch = commentImageService.saveBatch(commentImages);
                if (!saveBatch) {
                    throw new YunscException("保存订单评价图片失败");
                }
            }
            // 3、更新订单商品状态
            UpdateWrapper<YunscOrderGoodsEntity> updateOrderGoodsWrapper = new UpdateWrapper<YunscOrderGoodsEntity>()
                    .eq("order_goods_id", commentForm.getOrderGoodsId())
                    .eq("user_id", userId)
                    .eq("store_id", order.getStoreId())
                    .set("is_comment", 1);
            boolean update = orderGoodsService.update(updateOrderGoodsWrapper);
            if (!update) {
                throw new YunscException("更新订单商品状态失败");
            }
        }

        // 4、更新订单状态
        order.setIsComment(1);
        boolean updateOrderStatus = this.updateById(order);

        if (!updateOrderStatus) {
            throw new YunscException("更新订单状态失败");
        }

    }

    @Override
    public OrderOverviewVO queryOrderOverview(Integer storeId) {

        List<YunscOrderEntity> salesByToday = this.queryOrderSalesByToday();
        List<YunscOrderEntity> salesByYesterday = this.queryOrderSalesByYesterday();
        // 昨日数据 销售额 (元)
        BigDecimal priceYesterday = salesByYesterday.stream().map(order -> new BigDecimal(order.getPayPrice()))
                .reduce(BigDecimal.ZERO, BigDecimal::add);
        // 昨日支付订单数
        long payOrdersYesterday = salesByYesterday.stream().filter(order -> order.getPayStatus() == 20).count();
        // 昨日付款会员数
        long payUsersYesterday = salesByYesterday.stream().filter(order -> order.getPayStatus() == 20)
                .map(YunscOrderEntity::getUserId)
                .distinct().count();

        // 计算
        // 今日数据 销售额 (元)
        BigDecimal priceToday = salesByToday.stream().map(order -> new BigDecimal(order.getPayPrice()))
                .reduce(BigDecimal.ZERO, BigDecimal::add)
                .setScale(2, RoundingMode.HALF_UP);
        // 今日付款会员数
        long payUsersToday = salesByToday.stream().filter(order -> order.getPayStatus() == 20)
                .map(YunscOrderEntity::getUserId)
                .distinct().count();
        // 今日支付订单数
        long payOrdersToday = salesByToday.stream().filter(order -> order.getPayStatus() == 20).count();
        // 新增会员数
        Map<String, Object> userByDay = storeService.queryNewUserByday(storeId);
        String userByToday = (String) userByDay.get("tday");
        String userByYesterday = (String) userByDay.get("ytd");

        return new OrderOverviewVO(
                priceYesterday, priceToday,
                payOrdersYesterday, payOrdersToday,
                userByYesterday, userByToday,
                payUsersYesterday, payUsersToday
        );
    }

    @Override
    public TradeTrendVO queryOrderTradeTrend(Integer storeId) {
        List<OrderTradeTrendVO> trendList = this.baseMapper.getTradeTrendItems(storeId);
        // 初始化TradeTrendVO对象
        TradeTrendVO trend = new TradeTrendVO();
        List<String> dateList = new ArrayList<>();
        List<String> orderTotalList = new ArrayList<>();
        List<String> orderTotalPriceList = new ArrayList<>();
        // 初始化日期和数据列表
        for (int i = 6; i >= 0; i--) {
            String date = LocalDate.now().minusDays(i).format(DateTimeFormatter.ofPattern("yyyy-MM-dd"));
            dateList.add(date);
            orderTotalList.add("0");
            orderTotalPriceList.add(String.valueOf(BigDecimal.ZERO));
        }
        // 将查询结果填充到对应的位置
        for (OrderTradeTrendVO item : trendList) {
            String date = item.getDate();
            int index = dateList.indexOf(date);
            if (index != -1) {
                orderTotalList.set(index, item.getOrderTotal());
                orderTotalPriceList.set(index, item.getOrderTotalPrice());
            }
        }
        trend.setDate(dateList);
        trend.setOrderTotal(orderTotalList);
        trend.setOrderTotalPrice(orderTotalPriceList);

        return trend;
    }

    @Override
    public ConsumptionVO queryConsumption(Integer currentStoreId) {
        LambdaQueryWrapper<YunscOrderEntity> lqw1 = new LambdaQueryWrapper<YunscOrderEntity>()
                .eq(YunscOrderEntity::getStoreId, currentStoreId)
                .eq(YunscOrderEntity::getPayStatus, 20)
                .eq(YunscOrderEntity::getIsDelete, 0)
                .groupBy(YunscOrderEntity::getUserId);
        // 消费用户总数
        int consumerCount = this.list(lqw1).size();
        // 订单总数
        LambdaQueryWrapper<YunscOrderEntity> lqw2 = new LambdaQueryWrapper<YunscOrderEntity>()
                .eq(YunscOrderEntity::getStoreId, currentStoreId)
                .eq(YunscOrderEntity::getPayStatus, 20)
                .eq(YunscOrderEntity::getIsDelete, 0);
        int orderCount = this.count(lqw2);
        // 商品总数
        int goodsTotalCount = goodsService.queryGoodsTotalCount(0, 0, currentStoreId);
        // 用户总数
        int userTotalCount = userService.queryUserTotalCount(0, 0, currentStoreId);
        ConsumptionVO consumptionVO = new ConsumptionVO();
        consumptionVO.setConsumeUserTotal(String.valueOf(consumerCount));
        consumptionVO.setGoodsTotal(String.valueOf(goodsTotalCount));
        consumptionVO.setOrderTotal(String.valueOf(orderCount));
        consumptionVO.setUserTotal(String.valueOf(userTotalCount));
        return consumptionVO;
    }

    @Override
    public OrderPendingVO queryOrderPending(Integer currentStoreId) {
        // 获取订单等待发货数量
        LambdaQueryWrapper<YunscOrderEntity> lqw1 = new LambdaQueryWrapper<>();
        lqw1.eq(YunscOrderEntity::getStoreId, currentStoreId)
                .eq(YunscOrderEntity::getOrderStatus, 10)
                .eq(YunscOrderEntity::getPayStatus, 20)
                .eq(YunscOrderEntity::getDeliveryStatus, 10)
                .eq(YunscOrderEntity::getIsDelete, 0);
        int deliverOrderTotal = this.count(lqw1);
        // 售后单(笔)
        LambdaQueryWrapper<YunscOrderRefundEntity> lqw2 = new LambdaQueryWrapper<>();
        lqw2.eq(YunscOrderRefundEntity::getStoreId, currentStoreId)
                .eq(YunscOrderRefundEntity::getStatus, 0);
        long refundTotal = orderRefundService.count(lqw2);
        // 待付款订单(笔)
        LambdaQueryWrapper<YunscOrderEntity> lqw3 = new LambdaQueryWrapper<>();
        lqw3.eq(YunscOrderEntity::getStoreId, currentStoreId)
                .eq(YunscOrderEntity::getOrderStatus, 10)
                .eq(YunscOrderEntity::getPayStatus, 10)
                .eq(YunscOrderEntity::getIsDelete, 0);
        long paidOrderTotal = this.count(lqw3);
        // 获取已售罄商品数量
        int soldOutGoodsTotal = goodsService.querySoldOutGoodsTotal(currentStoreId);
        return new OrderPendingVO(
                String.valueOf(deliverOrderTotal),
                String.valueOf(refundTotal),
                String.valueOf(paidOrderTotal),
                String.valueOf(soldOutGoodsTotal)
        );
    }

    @Override
    public OverviewVO queryOverview(Integer storeId) {
        ConsumptionVO consumptionVO = this.queryConsumption(storeId);
        OverviewVO overview = new OverviewVO();
        // 会员数量
        overview.setUserTotal(consumptionVO.getUserTotal());
        // 消费人数
        overview.setConsumeUsers(consumptionVO.getConsumeUserTotal());
        // 支付订单数 (笔)
        overview.setOrderTotal(consumptionVO.getOrderTotal());
        // 商品数量 (件)
        overview.setGoodsTotal(consumptionVO.getGoodsTotal());
        // 销售额 (元)
        String salesTotal = this.baseMapper.querySalesTotal(storeId);
        overview.setOrderTotalPrice(salesTotal);
        // 用户充值总额 (元)
        String rechargeTotal = rechargeOrderDao.selectRechargeTotal(0, 0, storeId);
        overview.setRechargeTotalMoney(rechargeTotal == null ? "0.00" : rechargeTotal);

        return overview;
    }

    @Override
    public List<UserExpendRankingVO> queryUserExpendRanking(Integer storeId) {
       return this.baseMapper.selectUserExpendRanking(storeId);
    }

    @Override
    public OverviewVO queryOverviewByDate(String startDate, String endDate, Integer storeId) {
        int startInSeconds = DateUtils.convertIntToSeconds(startDate);
        int endInSeconds = DateUtils.convertIntToSeconds(endDate);
        // 订单消费概况
        OverviewVO overview = this.baseMapper.selectOverviewByDate(startInSeconds, endInSeconds, storeId);

        // 商品数量 (件)
        int goodsTotalCount = goodsService.queryGoodsTotalCount(startInSeconds, endInSeconds, storeId);
        overview.setGoodsTotal(String.valueOf(goodsTotalCount));

        // 用户总数
        int userTotalCount = userService.queryUserTotalCount(startInSeconds, endInSeconds, storeId);
        overview.setUserTotal(String.valueOf(userTotalCount));

        // 用户充值总额 (元)
        String rechargeTotal = rechargeOrderDao.selectRechargeTotal(startInSeconds, endInSeconds, storeId);
        overview.setRechargeTotalMoney(rechargeTotal == null ? "0.00" : rechargeTotal);

        return overview;
    }


    public List<YunscOrderEntity> queryOrderSalesByYesterday() {
        // 获取当前日期前一天的日期
        LocalDate yesterday = LocalDate.now().minus(1, ChronoUnit.DAYS);
        // 计算昨天开始时间（0点0分0秒）的时间戳
        LocalDateTime startOfYesterday = yesterday.atStartOfDay();
        long yesterdayStartInSeconds = startOfYesterday.toEpochSecond(ZoneOffset.UTC);
        // 计算昨天结束时间（23点59分59秒）的时间戳
        LocalDateTime endOfYesterday = yesterday.plusDays(1).atStartOfDay().minusSeconds(1);
        long yesterdayEndInSeconds = endOfYesterday.toEpochSecond(ZoneOffset.UTC);
        return getOrderEntityList(yesterdayStartInSeconds, yesterdayEndInSeconds);
    }

    public List<YunscOrderEntity> queryOrderSalesByToday() {
        // 获取当天的订单量
        // 获取当前日期
        LocalDate today = LocalDate.now();
        // 当天开始时间（0点0分0秒）
        LocalDateTime startOfDay = today.atStartOfDay();
        long startInSeconds = startOfDay.toEpochSecond(ZoneOffset.UTC);
        // 当天结束时间（23点59分59秒）
        LocalDateTime endOfDay = today.atTime(23, 59, 59);
        long endInSeconds = endOfDay.toEpochSecond(ZoneOffset.UTC);
        return getOrderEntityList(startInSeconds, endInSeconds);
    }

    private List<YunscOrderEntity> getOrderEntityList(long startInSeconds, long endInSeconds) {
        LambdaQueryWrapper<YunscOrderEntity> lqw = new LambdaQueryWrapper<>();
        lqw.eq(YunscOrderEntity::getPayStatus, 20);
        lqw.between(YunscOrderEntity::getCreateTime, startInSeconds, endInSeconds);
        return this.list(lqw);
    }

    // 设置订单状态文字
    private void setOrderStateText(OrderDetailVO order) {
        if (order.getPayStatus() == 10 && order.getOrderStatus() == 10) {
            order.setStateText("待支付");
        } else if (order.getPayStatus() == 20 && order.getDeliveryStatus() == 10 && order.getOrderStatus() == 10) {
            order.setStateText("待发货");
        } else if (order.getPayStatus() == 20 && order.getDeliveryStatus() == 30 && order.getOrderStatus() == 10) {
            order.setStateText("部分发货");
        } else if (order.getPayStatus() == 20 && order.getDeliveryStatus() == 20 && order.getReceiptStatus() == 10 && order.getOrderStatus() == 10) {
            order.setStateText("待收货");
        } else if (order.getOrderStatus() == 30) {
            order.setStateText("已完成");
        } else if (order.getOrderStatus() == 21) {
            order.setStateText("待取消");
        } else if (order.getOrderStatus() == 20) {
            order.setStateText("已取消");
        }


    }

    // 格式化更新价格
    public static Map<String, String> formatUpdatePrice(String updatePrice) {
        Map<String, String> map = new HashMap<>();
        BigDecimal decimal = new BigDecimal("0.00");
        BigDecimal decimal_price = new BigDecimal(updatePrice).setScale(2, BigDecimal.ROUND_HALF_UP);
        if (decimal.compareTo(decimal_price) < 0) {
            map.put("symbol", "-");
        } else {
            map.put("symbol", "+");
        }
        map.put("value", String.valueOf(decimal_price));
        return map;
    }
}